<!DOCTYPE html>
<html lang="zh-CN">
<head>
    <meta charset="UTF-8">
    <meta name="viewport" content="width=device-width, initial-scale=1.0">
    <title>图片放大镜</title>
    <style>
        .container {
            display: flex;
            gap: 20px;
            /* padding: 20px; */
        }
        
        .small-image-container {
            position: relative;
            display: inline-block;
            overflow: hidden;
        }
        
        #small-img {
            display: block;
            width: 800px;
            height: auto;
        }
        
        #mask {
            position: absolute;
            width: 150px;
            height: 150px;
            background-color: rgba(255, 255, 255, 0.3);
            border: 1px solid rgba(0, 0, 0, 0.3);
            display: none;
            pointer-events: none;
        }
        
        .big-image-container {
            width: 500px;
            height: 500px;
            overflow: hidden;
            display: none;
            border: 1px solid #ddd;
        }
        
        #big-canvas {
            display: block;
            width: 100%;
            height: 100%;
        }
    </style>
</head>
<body>
    <div class="container">
        <div class="small-image-container">
            <img id="small-img" src="https://i1.hdslb.com/bfs/archive/4cd073959d19fc314331f51f85d56fa23004d60a.jpg" alt="小图">
            <div id="mask"></div>
        </div>
        <div id="big-image" class="big-image-container">
            <canvas id="big-canvas"></canvas>
        </div>
    </div>
    <script>
        document.addEventListener('DOMContentLoaded', function() {
            const smallImg = document.getElementById('small-img');
            const mask = document.getElementById('mask');
            const bigImage = document.getElementById('big-image');
            const bigCanvas = document.getElementById('big-canvas');
            const ctx = bigCanvas.getContext('2d');
            
            // 设置canvas尺寸
            bigCanvas.width = 200;
            bigCanvas.height = 200;
            bigImage.width = 200;
            bigImage.height = 200;
            
            // 放大倍数
            // const zoomFactor = 3;
            const zoomFactor = bigCanvas.width / mask.offsetWidth;
            
            // 确保图片已加载
            smallImg.onload = function() {
                initMagnifier();
            };
            
            if (smallImg.complete) {
                initMagnifier();
            }
            
            function initMagnifier() {
                const smallRect = smallImg.getBoundingClientRect();
                const smallWidth = smallImg.offsetWidth;
                const smallHeight = smallImg.offsetHeight;
                bigCanvas.width = 200;
                bigCanvas.height = 200;
                bigImage.width = 200;
                bigImage.height = 200
                
                // 鼠标悬停显示遮罩和大图容器
                smallImg.parentElement.addEventListener('mouseover', () => {
                    mask.style.display = 'block';
                    bigImage.style.display = 'block';
                });
                
                // 鼠标移出隐藏遮罩和大图容器
                smallImg.parentElement.addEventListener('mouseout', () => {
                    mask.style.display = 'none';
                    bigImage.style.display = 'none';
                });
                
                // 鼠标移动处理函数
                smallImg.parentElement.addEventListener('mousemove', (e) => {
                    // 计算鼠标在小图中的相对位置
                    let x = e.clientX - smallRect.left - mask.offsetWidth / 2;
                    let y = e.clientY - smallRect.top - mask.offsetHeight / 2;
                    
                    // 限制遮罩在小图范围内
                    const maxX = smallWidth - mask.offsetWidth;
                    const maxY = smallHeight - mask.offsetHeight;
                    x = Math.max(0, Math.min(x, maxX));
                    y = Math.max(0, Math.min(y, maxY));
                    
                    // 设置遮罩的位置
                    mask.style.left = `${x}px`;
                    mask.style.top = `${y}px`;
                    
                    // 计算实际图片中的位置 (考虑小图的缩放比例)
                    const scaleX = smallImg.naturalWidth / smallWidth;
                    const scaleY = smallImg.naturalHeight / smallHeight;
                    
                    // 计算要放大的区域
                    const sourceX = x * scaleX;
                    const sourceY = y * scaleY;
                    const sourceWidth = mask.offsetWidth * scaleX;
                    const sourceHeight = mask.offsetHeight * scaleY;
                    
                    // 清除canvas
                    ctx.clearRect(0, 0, bigCanvas.width, bigCanvas.height);
                    
                    // 绘制放大后的图像
                    ctx.drawImage(
                        smallImg,
                        sourceX, sourceY, sourceWidth, sourceHeight, // 源图像裁剪区域
                        0, 0, bigCanvas.width, bigCanvas.height      // canvas绘制区域
                    );
                });
            }
        });
    </script>
</body>
</html>